#pragma once

#include <regex>
#include <string>
#include <string_view>  // TODO: 改用string_view解析HTTP请求
#include <unordered_map>
#include <unordered_set>


#include "Buffer.h"
#include "Common.h"


class HTTPRequest {
public:
    // 状态机状态
    enum class PARSE_STATE {
        REQUEST_LINE,      // 请求行
        REQUEST_HEAD,      // 请求头
        REQUEST_BODY,      // 请求体
        REQUEST_DONE       // 解析完成
    };

#if 0
    // TODO: 第二种方法，姑且先写在这（判断请求是否完整吗？）
    enum LINE_STATE {
        LINE_OK = 0,  // 读到一个完整的行
        LINE_BAD,     // 行出错
        LINE_OPEN     // 行数据不完整
    };
#endif

    HTTPRequest();

    ~HTTPRequest();

    void pares_request(const Buffer &request);

    bool pares_request_line(const std::string &line);

    void pares_request_head(const std::string &line);

    bool pares_request_body(const std::string &line);

    bool is_keep_alive() const;  // 判断是否保持连接

    const std::string &get_method() const;

    const std::string &get_url() const;

    const std::string &get_version() const;

    const std::string &get_body() const;

    const std::unordered_map<std::string, std::string> &get_request_header() const;

    const std::unordered_map<std::string, std::string> &get_request_body() const;

    HTTP_CODE get_http_code() const;

private:
    HTTP_CODE http_code;
    PARSE_STATE REQUEST_STATE;                                    // 表示状态机状态
    std::string method, url, version, body;                       // 请求行
    std::unordered_map<std::string, std::string> request_header;  // 请求头各个键值对的映射map
    std::unordered_map<std::string, std::string> request_body;    // 请求体各个键值对的映射map

};